package concursos.controladores;

import java.io.IOException;
import java.io.Serializable;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

import javax.ejb.EJB;
import javax.faces.application.FacesMessage;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ManagedProperty;
import javax.faces.bean.SessionScoped;
import javax.faces.context.FacesContext;
import javax.faces.event.ActionEvent;

import org.primefaces.event.ScheduleEntryMoveEvent;
import org.primefaces.event.ScheduleEntryResizeEvent;
import org.primefaces.event.SelectEvent;
import org.primefaces.model.DefaultScheduleEvent;
import org.primefaces.model.DefaultScheduleModel;
import org.primefaces.model.ScheduleEvent;
import org.primefaces.model.ScheduleModel;

import concursos.interfaces.ArquivoService;
import concursos.interfaces.ConcursoService;
import concursos.interfaces.LembreteService;
import concursos.modelos.Concurso;
import concursos.modelos.Lembrete;
import concursos.modelos.Usuario;

@ManagedBean
@SessionScoped
public class ScheduleController implements Serializable {

	private static final long serialVersionUID = 237305666769182947L;

	private ScheduleModel eventModel;
	private ScheduleEvent event = new DefaultScheduleEvent();
	@ManagedProperty(value = "#{concursoMB}")
	private ConcursoMB concursoMb;
	@ManagedProperty(value = "#{lembreteMB}")
	private LembreteMB lembreteMb;
	@EJB
	private ArquivoService beanArquivo;
	@EJB
	private ConcursoService beanConcurso;
	@EJB
	private LembreteService beanLembrete;
	private List<Concurso> listaConcursos;
	@ManagedProperty(value = "#{usuarioMB}")
	private UsuarioMB usuarioMB;
	private List<Lembrete> listaLembretes;
	private Usuario usuario;
	private Lembrete lembrete = new Lembrete();
	private int id_usuario, id_concurso_selecionado;
	private Concurso concurso = null;

	public ScheduleController() {
		this.eventModel = new DefaultScheduleModel();
		this.listaConcursos = new ArrayList<Concurso>();

		Object user = (Usuario) FacesContext.getCurrentInstance()
				.getExternalContext().getSessionMap().get("usuario");
		this.usuario = (Usuario) user;
		this.id_usuario = usuario.getId();
	}

	public void listarConcursos() throws IOException {
		this.listaConcursos = new ArrayList<Concurso>();
		this.listaLembretes = new ArrayList<Lembrete>();
		this.eventModel = new DefaultScheduleModel();

		this.listaConcursos = this.beanConcurso
				.listarConcursos(this.id_usuario);
		this.listaLembretes = this.beanLembrete
				.listarLembretes(this.id_usuario);

		for (Concurso c : this.listaConcursos) {
			DefaultScheduleEvent evento;

			evento = new DefaultScheduleEvent(c.getNome(), c.getDataProva(),
					c.getDataProva(), "style1");

			eventModel.addEvent(evento);
		}

		for (Lembrete l : this.listaLembretes) {
			DefaultScheduleEvent evento;

			evento = new DefaultScheduleEvent(l.getTitulo(),
					l.getDataLembrar(), l.getDataLembrar(), "style2");

			eventModel.addEvent(evento);
		}

		FacesContext.getCurrentInstance().getExternalContext()
				.redirect("calendario.xhtml");

	}

	public Usuario getUsuario() {
		return this.usuario;
	}

	public void setUsuario(Usuario usuario) {
		this.usuario = usuario;
	}

	public int getId_usuario() {
		return this.id_usuario;
	}

	public void setId_usuario(int id_usuario) {
		this.id_usuario = id_usuario;
	}

	public Date getInitialDate() {
		Calendar calendar = Calendar.getInstance();
		calendar.set(calendar.get(Calendar.YEAR), Calendar.FEBRUARY,
				calendar.get(Calendar.DATE), 0, 0, 0);

		return calendar.getTime();
	}

	public ScheduleModel getEventModel() {
		return eventModel;
	}

	public ScheduleEvent getEvent() {
		return event;
	}

	public void setEvent(ScheduleEvent event) {
		this.event = event;
	}

	public void addEvent(ActionEvent actionEvent) throws Exception {
		FacesContext context = FacesContext.getCurrentInstance();
		Date data = new Date();
		SimpleDateFormat formatador = new SimpleDateFormat("dd/MM/yyyy");

		this.lembrete.setConcurso(this.beanConcurso
				.buscaPorId(this.id_concurso_selecionado));

		if (!(this.lembrete.getConcurso() == null)) {
			if (this.lembrete.isEnviarEmail()) {
				if (this.event.getStartDate().before(data)
						|| formatador.format(data).equals(
								formatador.format(this.event.getStartDate())))
					context.addMessage(null, new FacesMessage(
							FacesMessage.SEVERITY_ERROR, "Aviso",
							"Agende para uma data posterior a atual"));
				else {
					this.cadastarLembrete(this.lembrete);
				}

			} else {
				try {
					this.cadastarLembrete(this.lembrete);
				} catch (Exception exception) {
				}
			}
		} else
			context.addMessage(null, new FacesMessage(
					FacesMessage.SEVERITY_ERROR, "Aviso",
					"Nenhum concurso selecionado."));

	}

	public void onEventSelect(SelectEvent selectEvent) {
		this.concurso = new Concurso();
		event = (ScheduleEvent) selectEvent.getObject();
		for (Concurso c : this.listaConcursos) {
			if (c.getNome().equalsIgnoreCase(event.getTitle())) {
				this.concurso = beanConcurso.buscarPorNome(c.getNome());

				try {
					this.exibirDetalhesConcurso(this.concurso);
				} catch (IOException exception) {
				}
			}
		}
	}

	private void exibirDetalhesConcurso(Concurso c) throws IOException {
		this.concursoMb.setListaArquivos(this.beanArquivo
				.listarArquivosPorConcurso(c.getId()));
		this.concursoMb.exibirDetalhesConcurso(c);
	}

	public void onDateSelect(SelectEvent selectEvent) {
		event = new DefaultScheduleEvent("", (Date) selectEvent.getObject(),
				(Date) selectEvent.getObject());
	}

	private void cadastarLembrete(Lembrete lembrete) throws Exception {
		this.lembreteMb.setConcursoSelecionado(this.beanConcurso
				.buscaPorId(this.id_concurso_selecionado));

		this.lembrete.setDataLembrar(this.event.getStartDate());
		this.lembreteMb.setLembrete(lembrete);

		this.lembreteMb.cadastrarLembrete();

		this.lembrete = new Lembrete();
		this.listarConcursos();
	}

	public void onEventMove(ScheduleEntryMoveEvent event) {
		FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO,
				"Event moved", "Day delta:" + event.getDayDelta()
						+ ", Minute delta:" + event.getMinuteDelta());

		addMessage(message);
	}

	public void onEventResize(ScheduleEntryResizeEvent event) {
		FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO,
				"Event resized", "Day delta:" + event.getDayDelta()
						+ ", Minute delta:" + event.getMinuteDelta());

		addMessage(message);
	}

	private void addMessage(FacesMessage message) {
		FacesContext.getCurrentInstance().addMessage(null, message);
	}

	public ConcursoMB getConcursoMb() {
		return this.concursoMb;
	}

	public void setConcursoMb(ConcursoMB concursoMb) {
		this.concursoMb = concursoMb;
	}

	public LembreteMB getLembreteMb() {
		return this.lembreteMb;
	}

	public void setLembreteMb(LembreteMB lembreteMb) {
		this.lembreteMb = lembreteMb;
	}

	public Lembrete getLembrete() {
		return this.lembrete;
	}

	public void setLembrete(Lembrete lembrete) {
		this.lembrete = lembrete;
	}

	public int getId_concurso_selecionado() {
		return this.id_concurso_selecionado;
	}

	public void setId_concurso_selecionado(int id_concurso_selecionado) {
		this.id_concurso_selecionado = id_concurso_selecionado;
	}

	public Concurso getConcurso() {
		return this.concurso;
	}

	public void setConcurso(Concurso concurso) {
		this.concurso = concurso;
	}

	public List<Concurso> getListaConcursos() {
		return this.listaConcursos;
	}

	public void setListaConcursos(List<Concurso> listaConcursos) {
		this.listaConcursos = listaConcursos;
	}

	public List<Lembrete> getListaLembretes() {
		return this.listaLembretes;
	}

	public void setListaLembretes(List<Lembrete> listaLembretes) {
		this.listaLembretes = listaLembretes;
	}

	public UsuarioMB getUsuarioMB() {
		return this.usuarioMB;
	}

	public void setUsuarioMB(UsuarioMB usuarioMB) {
		this.usuarioMB = usuarioMB;
	}
}